package com.springday3aop.aop;

import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.*;
import org.springframework.stereotype.Component;

@Component // 声明是一个Spring组件，如果不声明切面功能会失效
@Aspect // 声明是一个切面类
public class MyAdvice {

    // 定义切入点表达式，匹配update()方法
    // execution表示执行该方法时切入
    @Pointcut("execution(* com.springday3aop.*.*Dao.update(..))")
    private void pt() {
    }

    ;

    @Pointcut("execution(* com.springday3aop.*.*Dao.select(..))")
    private void pt2() {
    }

    ;

    @Pointcut("execution(* com.springday3aop.dao.BookDao.find(..))")
    private void pt3() {
    }

    ;

    //    前置通知，在切入点方法执行前执行。
    @Before("pt()")
    public void method() {
        System.out.println("Before...");
    }

    //    后置通知
    @After("pt()")
    public void method2() {
        System.out.println("After...");
    }

    //    环绕通知
    @Around("pt2()")
    public void method3(ProceedingJoinPoint pjp) throws Throwable {
        System.out.println("around Before...");
        pjp.proceed();
        System.out.println("around After...");
    }

    //    环绕通知的连接点有返回值
    @Around("pt3()")
    public Object method4(ProceedingJoinPoint pjp) throws Throwable {
        System.out.println("around Before...2");
        Object obj = pjp.proceed();
        System.out.println("around After...2");
        return obj;
    }
}
